<?php

class Core_Html_Form_ComboTree extends Kd_Html_Form_Element {

    private $_dataSource = NULL;
    private $_multiple = FALSE;
    private $_size = 1;
    private $_treeData = NULL;
    private $_defaultOption = NULL;

    public function __construct() {
        parent::__construct();
        $this->templateName = 'form/combotree';
        $this->addClass('input');
    }

    public function getSize() {
        return $this->_size;
    }

    public function setSize($value) {
        $this->_size = $value;
        return $this;
    }

    public function getMultiple() {
        return $this->_multiple;
    }

    public function setMultiple($value) {
        $this->_multiple = $value;
        return $this;
    }

    public function setDefaultOption($value, $text){
        $this->_defaultOption = array('value'=>$value, 'text'=>$text);
        return $this;
    }
    public function getDefaultOption(){
        return $this->_defaultOption;
    }

    public function getTreeData() {
        return $this->_treeData;
    }

    public function setDataSource($value) {
        $this->_dataSource = $value;
    }

    public function getDataSource() {
        return $this->_dataSource;
    }

    public function bindData($datas, $startValue, array $itemKeys) {
        $this->setDataSource($datas);
        $this->_treeData = $this->buildTreeData($startValue, $itemKeys, 0);
        return $this;
    }

    private function buildTreeData($parentValue, $itemKeys, $level) {
        $result = array();
        for ($i = 0; $i < count($this->_dataSource); $i++) {
            $item = $this->_dataSource[$i];
            if ($item[$itemKeys['parentKey']] == $parentValue) {
                $children = $this->buildTreeData($item[$itemKeys['childKey']], $itemKeys, $level + 1);
                $treeItem = array(
                    'id' => $item[$itemKeys['valueKey']],
                    'text' => str_pad($item[$itemKeys['textKey']], $level + strlen($item[$itemKeys['textKey']]), '-', STR_PAD_LEFT),
                    'disabled' => isset($itemKeys['disabledKey']) ? $item[$itemKeys['disabledKey']] : FALSE
                );
                if (count($children) > 0) {
                    $treeItem['children'] = $children;
                }
                $result[] = $treeItem;
            }
        }
        return $result;
    }

    protected function renderReadonly() {
        return '';
    }

    protected function renderEditable() {
        if (!$this->getEnabled()) {
            $this->addClass('disabled');
        }

        $this->setAttribute('id', $this->getId())
                ->setAttribute('name', $this->getName());
        if ($this->getSize() > 1) {
            $this->setAttribute('size', $this->getSize());
        }
        if (!$this->getEnabled()) {
            $this->setAttribute('disabled', 'disabled');
        }
        if ($this->getMultiple()) {
            $this->setAttribute('multiple', 'multiple');
        }

        $selectedValues = is_array($this->getValue()) ? $this->getValue() : array($this->getValue());
        $result = '<select ' . $this->getAttributeHtml() . '>';
        if(!is_null($this->_defaultOption)){
            $result .= '<option value="' . $this->_defaultOption['value'] . '">' . $this->_defaultOption['text'] . '</option>';
        }
        $result .= $this->createOptionHtml($this->_treeData, $selectedValues);
        return $result . '</select>';
    }

    private function createOptionHtml($datas, $selectedValues) {
        $result = '';
        foreach ($datas as $data) {
            $selected = '';
            if (!empty($selectedValues)) {
                foreach ($selectedValues as $sv) {
                    if (strlen($sv) == strlen($data['id']) && $sv == $data['id']) {
                        $selected = ' selected="selected"';
                    }
                }
            }
            $result .= '<option value="' . $data['id'] . '"' . $selected . '>' . $data['text'] . '</option>';
            if (array_key_exists('children', $data)) {
                $result .= $this->createOptionHtml($data['children'], $selectedValues);
            }
        }
        return $result;
    }

}